package senke;

import java.io.IOException;
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.UnknownHostException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

import util.DataLogger;
import util.DataPackage;
/**
 * DataSink
 * Waits for data to come in via UDP and prints it to the console.
 * Creates a logfile.
 * 
 * @author Jan Quenzel
 * @author Rico Flaegel
 */
public class DataSink implements Runnable{
	/**
	 * the listen port
	 */
	private int port;
	/**
	 * Socket for receive
	 */
	private DatagramSocket sock;
	/**
	 * the file logger
	 */
	private DataLogger logger;
	
	public DataSink(int port){
		this.port = port;
	}
	
	/**
	 * starts the DataSink
	 * @param args parameter is the listen port
	 */
	public static void main(String[] args) {
		try{
			if(args.length == 1){
				int port = Integer.parseInt(args[0]);
				DataSink sr = new DataSink(port);
				ExecutorService exec = Executors.newSingleThreadExecutor();
				exec.execute(sr);
				exec.shutdown();
			}else{
				throw new NumberFormatException();
			}
		}catch(NumberFormatException e){
			System.err.println("Wrong number of Input parameters... Usage: DataSink <port>");
		}
	}

	@Override
	/**
	 * listen on the port, get incoming messages and store the information in the file
	 */
	public void run() {
		try {
			this.logger = new DataLogger(port+"_DataSinkLog.txt");
			sock = new DatagramSocket(port);
			byte[] b = new byte[DataPackage.len];
			DatagramPacket rdp = new DatagramPacket(b,b.length);
			DataPackage dp = new DataPackage();
			long timestamp = 0;
			while(true){
				sock.receive(rdp);
				timestamp = System.currentTimeMillis();
				dp.fromByte(rdp.getData());
				String s = dp.toString() + " at " + timestamp;
				System.out.println(s);
				logger.logString(s);
			}
		} catch (UnknownHostException e) {
			e.printStackTrace();
		} catch (IOException e1) {
			e1.printStackTrace();
		} finally{
			if( sock != null) sock.close();
		}
	}
}
